package com.example.performance.jmh.annotation;

import org.openjdk.jmh.annotations.Benchmark;
import org.openjdk.jmh.annotations.BenchmarkMode;
import org.openjdk.jmh.annotations.Mode;
import org.openjdk.jmh.runner.Runner;
import org.openjdk.jmh.runner.RunnerException;
import org.openjdk.jmh.runner.options.Options;
import org.openjdk.jmh.runner.options.OptionsBuilder;
import org.openjdk.jmh.runner.options.TimeValue;

import java.util.concurrent.TimeUnit;

/**
 * @author zpMeng
 * @since 9/18/2024
 */

@BenchmarkMode(Mode.All)
public class A1BenchMarkMode {

    @Benchmark
    public double getInt() {
        return 1D;
    }

    public static void main(String[] args) throws RunnerException {
        Options options = new OptionsBuilder().include(A1BenchMarkMode.class.getSimpleName())
                .forks(1)
                .warmupIterations(3)
                .warmupTime(TimeValue.seconds(1))
                .measurementIterations(3)
                .measurementTime(TimeValue.seconds(1))
                .timeUnit(TimeUnit.NANOSECONDS)
                .build();
        new Runner(options).run();
    }

    @BenchmarkMode(Mode.Throughput)
    public static class Throughput extends A1BenchMarkMode {
        public static void main(String[] args) throws RunnerException {
            Options options = new OptionsBuilder().include(Throughput.class.getSimpleName())
                    .forks(1)
                    .warmupIterations(3)
                    .warmupTime(TimeValue.seconds(1))
                    .measurementIterations(3)
                    .measurementTime(TimeValue.seconds(1))
                    .timeUnit(TimeUnit.NANOSECONDS)
                    .build();
            new Runner(options).run();
        }
    }

    @BenchmarkMode(Mode.AverageTime)
    public static class AverageTime extends A1BenchMarkMode {
        public static void main(String[] args) throws RunnerException {
            Options options = new OptionsBuilder().include(AverageTime.class.getSimpleName())
                    .forks(1)
                    .warmupIterations(3)
                    .warmupTime(TimeValue.seconds(1))
                    .measurementIterations(3)
                    .measurementTime(TimeValue.seconds(1))
                    .timeUnit(TimeUnit.NANOSECONDS)
                    .build();
            new Runner(options).run();
        }
    }

    @BenchmarkMode(Mode.SampleTime)
    public static class SampleTime extends A1BenchMarkMode {
        public static void main(String[] args) throws RunnerException {
            Options options = new OptionsBuilder().include(SampleTime.class.getSimpleName())
                    .forks(1)
                    .warmupIterations(3)
                    .warmupTime(TimeValue.seconds(1))
                    .measurementIterations(3)
                    .measurementTime(TimeValue.seconds(1))
                    .timeUnit(TimeUnit.NANOSECONDS)
                    .build();
            new Runner(options).run();
        }
    }

    @BenchmarkMode(Mode.SingleShotTime)
    public static class SingleShotTime extends A1BenchMarkMode {
        public static void main(String[] args) throws RunnerException {
            Options options = new OptionsBuilder().include(SingleShotTime.class.getSimpleName())
                    .forks(5)
                    .warmupIterations(0)
                    .measurementIterations(1)
                    .timeUnit(TimeUnit.NANOSECONDS)
                    .build();
            new Runner(options).run();
        }
    }

}
